Option Explicit
dim units, toolPath, toolDirection,toolEntryMode
dim xyFeedRate,zFeedRate,toolDiameter,maxDepthPerPass,TotalDepthOfCut
dim finishCutDepth, finishCutWidth,zRapidClearanceHeight, zInitialStartHeight
dim spindleSpeed, slotOrientation, coolant
dim xStart,slotLength,yStart,slotWidth
dim roughSlotLength,roughSlotWidth, radius
dim beginX, beginY
dim nextX, nextY
dim i, numberOfPasses,calculatedToolDiameter,entry
dim pi,slotAngle
dim finishSlotLength,finishSlotWidth
dim startAngle,endAngle, arcCenterPointX,arcCenterPointY, arcRadius
dim arcStartX,arcStartY,arcEndX,arcEndY,centerPointY,centerPointX
dim arcStartX1,arcStartY1,arcEndX1,arcEndY1
dim arcStartX2,arcStartY2,arcEndX2,arcEndY2
dim arcStartX3,arcStartY3,arcEndX3,arcEndY3
dim arcCalcRadius

 pi = 3.1415926535897932384626433832795

'setTicker 1, GetUserLed (1200) 
'------------------------------
' Get unit selection
'
if getUserLed (1200)  = 1 then
units = "G20"
else
units = "G21"
end if

'-------------------------------
' Get tool entry mode selection
'
if getUserLed (1206)  = 1 then
toolEntryMode = "plunge"
else
toolEntryMode = "ramp"
end if

'debug
'setUserLabel 1, "ToolEntryMode " & toolEntryMode

'-------------------------------
' Get slot orientation selection
'
if getUserLed (1208)  = 1 then
slotOrientation = "straight"
else
slotOrientation = "arc"
end if

'debug
'setUserLabel 1, "slotOrientation " & slotOrientation

'-------------------------------
' Get collant selection
'
if getUserLed (1210)  = 1 then
coolant = "M8"
else
coolant = "M9"
end if

'debug
'setUserLabel 1, "slotOrientation " & slotOrientation

'-------------------------------
' Get dro values
'
xyFeedRate = getOEMDRO (1100)
'question("xyFeedRate = " & xyFeedRate)

zFeedRate = getOEMDRO (1101)
toolDiameter = getOEMDRO (1102)
maxDepthPerPass = getOEMDRO (1103)
TotalDepthOfCut = getOEMDRO (1104)
finishCutDepth = getOEMDRO (1105)
finishCutWidth = getOEMDRO (1107)
zRapidClearanceHeight = getOEMDRO (1108)
zInitialStartHeight = getOEMDRO (1109)
xStart = getOEMDRO (1110)
slotLength = getOEMDRO (1111)
yStart = getOEMDRO (1112)
slotWidth = getOEMDRO (1113)
spindleSpeed = getOEMDRO (1114)
slotAngle = (pi/180) * getOEMDRO (1115)



startAngle = (pi/180) * getOEMDRO (1116)
endAngle = (pi/180) * getOEMDRO (1117)
arcCenterPointX = getOEMDRO (1118)
arcCenterPointY = getOEMDRO (1119)
arcRadius = getOEMDRO (1120)


beginX = xStart
beginY = yStart
nextX =  beginX + (slotLength-(slotWidth/2))*(cos (slotAngle))
nextY =  beginY + (slotLength-(slotWidth/2))*(sin (slotAngle))


roughSlotLength = slotLength
roughslotWidth = (slotWidth - (2*finishCutWidth)) - (toolDiameter)
finishSlotLength = slotLength
finishSlotWidth = slotWidth - toolDiameter

'====================================================
'calculate number of passes required
'adjust max depth per pass to match
'
numberOfPasses = (TotalDepthOfCut-finishCutDepth)/maxDepthPerPass
if numberOfPasses - int(numberOfPasses) <> 0 then
numberOfPasses = int(numberOfPasses)+1
maxDepthPerPass = (TotalDepthOfCut-finishCutDepth)/numberOfPasses
end if

calculatedToolDiameter = (toolDiameter/2)+(2*finishCutWidth)
radius = roughslotWidth/2
entry = radius * .9

OpenTeachFile "slot.tap"

code units
code "G17 G40 G80"
code "G00 Z"& zRapidClearanceHeight
code "G90 G54"
code "S" & spindleSpeed & " M03"


if slotOrientation = "arc" then

'centercut pass
'
arcStartX1 =  (arcCenterPointX + arcRadius) *(cos(startAngle)) 
arcStartY1 =  (arcCenterPointY + arcRadius) *(sin(startAngle)) 
arcEndX1 =  arcRadius*(cos (endAngle))
arcEndY1=  arcRadius*(sin (endAngle))

'question("ASX "& arcStartX1 & "ASY "& arcStartY1 )
'question("AEX "& arcEndX1 & "AEY "& arcEndY1)
call gencodeArc(arcStartX1,arcStartY1,arcEndX1,arcEndY1)

'now change radius by roughslotWidth/2************************************

arcStartX2 =  (arcRadius - roughslotWidth/2 + arcCenterPointX ) *(Cos (startAngle))
arcStartY2 =  (arcRadius - roughslotWidth/2 + arcCenterPointY) *(sin (startAngle))
arcEndX2 =  (arcRadius - roughslotWidth/2)*(Cos (endAngle))
arcEndY2=  (arcRadius - roughslotWidth/2)*(sin (endAngle)) 

call gencodeArc(arcStartX2,arcStartY2,arcEndX2,arcEndY2)

arcStartX3 =  (arcRadius + roughslotWidth/2 + arcCenterPointX ) *(Cos (startAngle))
arcStartY3 =  (arcRadius + roughslotWidth/2 + arcCenterPointY) *(sin (startAngle))
arcEndX3 =  (arcRadius + roughslotWidth/2)*(Cos (endAngle))
arcEndY3=  (arcRadius + roughslotWidth/2)*(sin (endAngle))

call gencodeArc(arcStartX3,arcStartY3,arcEndX3,arcEndY3)



else
	'====================================================
	'roughing pass
	'
	'
	call gencode(numberOfPasses,maxDepthPerPass,calculatedToolDiameter,entry,radius,roughSlotLength,roughSlotWidth)

	'====================================================
	'finish pass
	'
	'
	if finishCutDepth >0 or finishCutWidth >0 then

	numberOfPasses = 1
	maxDepthPerPass = TotalDepthOfCut
	calculatedToolDiameter = toolDiameter/2
	radius = finishSlotWidth/2
	entry = radius * .9
	call gencode(numberOfPasses,maxDepthPerPass,calculatedToolDiameter,entry,radius,finishSlotLength,finishSlotWidth)
	end if

end if
'---
'program end
'
code "G00 Z1.0"
if coolant = "M8" then
	code "M09"
	else
	code coolant
end if
code "M30"
closeTeachFile
call loadTeachFile

sub gencode(passCount,depthPerPass,calcToolDiameter,leadInLength,calcRadius,codeSlotLength,codeSlotWidth)

'-------------------------------
' Verfify input values
'

setTicker 1, ""

'setUserLabel 1, abs(slotLength)-(finishCutWidth*2)
if SlotLength <= toolDiameter then 
call error("Tool Diameter is larger than slot length")
exit sub
end if

if toolDiameter >= slotWidth-(finishCutWidth*2)then 
call error("Tool Diameter is too large for slot and finish pass ")
exit sub
end if

if (toolDiameter*3)< slotWidth+(finishCutWidth*2) then 
call error("Tool Diameter is too small to cut slot in 3 passes")
exit sub
end if

if zRapidClearanceHeight <= 0  then 
call error("Z rapid clearance height must be greater than 0")
exit sub
end if

if TotalDepthOfCut <= 0  then 
call error("Depth of cut is entered as a positive value and must be greater than 0")
exit sub
end if

if zRapidClearanceHeight < 0  then 
call error("Z initial move safe height is entered as a positive value and must be 0 or greater")
exit sub
end if

if zInitialStartHeight < 0  then 
call error("Z initial start height is entered as a positive value and must be 0 or greater")
exit sub
end if


if slotWidth > slotLength/2 then
call error("Slot length must be twice as long as slot width")
exit sub
end if

if finishCutWidth > toolDiameter*.1 then
call error("Finsh cut with must <= 10% of tool diameter")
exit sub
end if


'====================================================
' create code
'
'====================================================
' 
'

	code "G00 X" & beginX & " Y" & beginY
	code "G00 Z" & zInitialStartHeight
	code coolant
	
	code "G01 Z0 F" & zFeedRate
	
	
	if toolEntryMode = "ramp" then
	for i = 1 to passCount
		
		code "G01 X" & beginX & " Y" & beginY &" Z" & round(((depthPerPass*-1)*i),4) & " F" & xyFeedRate
		code "G01 X" & nextX & " Y" & nextY &" Z" & round(((depthPerPass*-1)*i),4) & " F" & xyFeedRate
	next
	else
	'plunge
	for i = 1 to passCount
		code "G01 Z" & round(((depthPerPass*-1)*i),4) & " F" & zFeedRate
		'if odd
		'
		if i mod 2 >0 then
		code "G01 X" & nextX & " Y" & nextY  & " F" & xyFeedRate
		else
		code "G01 X" & beginX & " Y" & beginY  & " F" & xyFeedRate
		end if
	next
	end if
	
	code "G00 Z0"
	
	'---
	'lead in path
	'
	code "(lead in)"
	code "G01 X" & nextX + (leadInLength*cos(slotAngle))-(calcRadius*.05*sin(slotAngle)) & " Y" & nextY+(leadInLength*sin(slotAngle))+(calcRadius*.05*cos(slotAngle)) & " F" & xyFeedRate
	code "G03 X"& nextX -calcRadius*sin(slotAngle)& " Y" & nextY + calcRadius*cos(slotAngle) & " R"& calcRadius-(calcRadius*.05)& " F" & xyFeedRate
	
	if toolEntryMode = "ramp" then
	for i = 1 to passCount
		code "G01 X" & beginX -calcRadius*sin(slotAngle)& " Y" & beginY + calcRadius*cos(slotAngle)&" Z" & round(((depthPerPass*-1)*i),4) & " F" & xyFeedRate
		code "G03 X" & beginX +calcRadius*sin(slotAngle) &" Y" & beginY - calcRadius*cos(slotAngle) & " R"& calcRadius
		code "G01 X" & nextX +calcRadius*sin(slotAngle)  &" Y" & nextY - calcRadius*cos(slotAngle)
		code "G03 X" & nextX -calcRadius*sin(slotAngle)& " Y" & nextY + calcRadius*cos(slotAngle)& " R"& calcRadius
	next
	'----
	'clean last sloped path so bottom is smooth and flat
	'
		code "G01 X" & beginX -calcRadius*sin(slotAngle)& " Y" & beginY + calcRadius*cos(slotAngle)& " F" & xyFeedRate
		code "G03 X" & beginX +calcRadius*sin(slotAngle) &" Y" & beginY - calcRadius*cos(slotAngle) & " R"& calcRadius
		code "G01 X" & nextX +calcRadius*sin(slotAngle)  &" Y" & nextY - calcRadius*cos(slotAngle)
		code "G03 X" & nextX -calcRadius*sin(slotAngle)& " Y" & nextY + calcRadius*cos(slotAngle)& " R"& calcRadius
	
	else 
	for i = 1 to passCount
		code "G01 Z" & round(((depthPerPass*-1)*i),4) & " F" & zFeedRate
		code "G01 X" & beginX &" F" & xyFeedRate
		code "G03 Y" & beginY + calcRadius & " R"& calcRadius
		code "G01 X" & nextX 
		code "G03 Y" & nextY - calcRadius & " R"& calcRadius
	next
	end if
	
	'---
	'exit path
	'
	'code "(lead out)"
	code "G03 X"& nextX- calcRadius*cos(slotAngle) & " Y"& nextY-calcRadius*sin(slotAngle) & " R" & calcRadius-(calcRadius*.05)
	code "G01 X" & beginX & " Y" & beginY

end sub



sub gencodeArc(arcStartX,arcStartY,arcEndX,arcEndY)


numberOfPasses = (totalDepthOfCut-finishCutDepth)/maxDepthPerPass
if numberOfPasses - int(numberOfPasses) <> 0 then
numberOfPasses = int(numberOfPasses)+1
maxDepthPerPass = (totalDepthOfCut-finishCutDepth)/numberOfPasses
end if

OpenTeachFile "CutArc.tap"


code "G00 Z1"
code "G00 X" & round(arcStartX,4) & " Y" & round(arcStartY,4)
code "G00 Z" & zRapidClearanceHeight
code "G01 Z0"
code "G01 X" & round(arcStartX,4) & " Y" & round(arcStartY,4)


for i = 1 to numberOfPasses
	'code "G3 X" & round(arcEndX,4) & " Y" & round(arcEndY,4) & " R"  & arcRadius & " F" & xyFeedRate&" Z" & round(((maxDepthPerPass*-1)*i),4)
	'code "G2 X" & round(arcStartX,4) & " Y" & round(arcStartY,4) & " R" & arcRadius & " F" & xyFeedRate
	
	centerPointX= arcCenterPointX - (arcCenterPointX + arcStartX)
	centerPointY = arcCenterPointY - (arcCenterPointY + arcStartY)
	code "G3 X" & round(arcEndX,4) & " Y" & round(arcEndY,4) & " I" & round(centerPointX,4)  & " J" & round(centerPointY,4) & " F" & xyFeedRate&" Z" & round(((maxDepthPerPass*-1)*i),4)
	

	centerPointX= arcCenterPointX - (arcCenterPointX + arcEndX)
	centerPointY = arcCenterPointY - (arcCenterPointY + arcEndY)
	code "G2 X" & round(arcStartX,4) & " Y" & round(arcStartY,4) & " I" & round(centerPointX,4)  & " J" & round(centerPointY,4) & " F" & xyFeedRate

next
	'----
	'clean last sloped path so bottom is smooth and flat
	'
	'centerPointX= arcCenterPointX - (arcCenterPointX + arcStartX)
	'centerPointY = arcCenterPointY - (arcCenterPointY + arcStartY)
	'code "G3 X" & round(arcEndX,4) & " Y" & round(arcEndY,4) & " I" & round(centerPointX,4)  & " J" & round(centerPointY,4) & " F" & xyFeedRate

	'centerPointX= arcCenterPointX - (arcCenterPointX + arcEndX)
	'centerPointY = arcCenterPointY - (arcCenterPointY + arcEndY)
	'code "G2 X" & round(arcStartX,4) & " Y" & round(arcStartY,4) & " I" & round(centerPointX,4)  & " J" & round(centerPointY,4) & " F" & xyFeedRate

code "G00 Z1"
code "G00 X"& round(arcCenterPointX,4)& " Y" & round(arcCenterPointY,4)

end sub

sub Error(msg)
call playWave("chimes.wav")
setTicker 1, "     " & msg
code"(" & msg & ")"
end sub